import { Component, OnInit, Injector, Input, ViewChild, Sanitizer } from '@angular/core';
import { DomSanitizer, SafeResourceUrl } from '@angular/platform-browser';
import { NgZorroPageBaseComponent } from '../../../core/ng-zorro-page-base-component/ng-zorro-page-base-component.component';
import {
  BaseComponentConfig, SystemFormControl, HttpService, LoadRemoteDataType,
  KeyValueOutput, RecordFormUpLoadFile, FieldType, DrillFormControl, RecordUploadFile
} from '../../..';
import { NzMessageService, NzModalService, UploadFile } from 'ng-zorro-antd';
import { FormBuilder, FormGroup, Validators } from '@angular/forms';
import { ActivatedRoute, Router } from '@angular/router';
import { Observable } from 'rxjs/Observable';
import { Observer } from 'rxjs/Observer';
import { HttpRequest, HttpClient, HttpResponse } from '@angular/common/http';
import { v4 as uuid } from 'uuid';
import { filter, map } from 'rxjs/operators';
import { environment } from 'environments/environment';
import { SignalRService } from '../../../core/service/singnalr-service';
import { Location } from "@angular/common";
import { GrillDataComponent } from '../../drill/grill-data/grill-data.component';

@Component({
  selector: 'app-drill-content',
  templateUrl: './drill-content.component.html',
  styleUrls: ['./drill-content.component.scss']
})
export class DrillContentComponent implements OnInit {
  // recordid
  recordId = 0;
  recordFlowId = 0;
  // 审核数据的流程下标
  reViewIndex = 0;
  _guideDocument = "";
  currentIndex;
  // fileList = new Array<RecordFormUpLoadFile>();
  fileList = {};
  _focusEntity = {};
  subjectId = 0;
  selectedTypeValue = "";
  errorMsgInfo = "";
  teacherScoreArray = [];

  /**
   * 获取指导文档内容
   */
  get guideDocument() {
    return this.sanitizer.bypassSecurityTrustHtml(this._guideDocument);
  }

  get focusEntity(): any {
    return this.getEntityFromFormGroup(this.validateForm, this._focusEntity);
  }

  set focusEntity(input: any) {
    this.setEntityToFormGroup(this.validateForm, input);
    this._focusEntity = input;
  }

  get getCurrentIndex(): number {
    return this.currentIndex > 0 ? this.currentIndex - 1 : 0;
  }

  get loginType() {

    return sessionStorage.getItem('userRoleType');
  }

  get docUrl(): SafeResourceUrl {
    return this.sanitizer.bypassSecurityTrustResourceUrl(
      this.httpService.IP_PORT + '?subjectid=' + this.subjectId + '&typeinfo=3');
  }



  // 服务等内容
  httpService: HttpService;
  message: NzMessageService;
  fb: FormBuilder;
  nzModalService: NzModalService;
  validateForm: FormGroup;
  validateForm_sp: FormGroup;
  route: ActivatedRoute;
  router: Router;
  nghttp: HttpClient;
  location: Location;

  isOperation = false;

  /**
    * 组件初始化
    */
  isSpinning = false;
  /**
 * 初始化订阅
 */
  GetDataObserver: Observable<any>;
  /**
 * 表单配置信息
 */
  arSystemFormControls: Array<DrillFormControl> = new Array<DrillFormControl>();
  arTableFormControls: Array<Array<DrillFormControl>> = new Array<Array<DrillFormControl>>();
  /**
   * 审批内容
   */
  // arSystemFormControls_sp: Array<DrillFormControl> = new Array<DrillFormControl>();
  // arTableFormControls_sp: Array<Array<DrillFormControl>> = new Array<Array<DrillFormControl>>();
  // _focusEntity_sp = {};
  // get focusEntity_sp(): any {
  //   return this._focusEntity_sp;
  // }

  // set focusEntity_sp(input: any) {
  //   this.setEntityToFormGroup(this.validateForm_sp, input);
  //   this._focusEntity_sp = input;
  // }
  // fileList_sp = new Array<any>();


  _pKeyFieldValue = 0;

  flowRecordOutput: any;
  opinion = '';

  arLogHistory = new Array<any>();
  // 实训知道变量
  rb; // box 元素
  rn; // 右侧按钮
  isVisible = false;
  testVal = 0;

  constructor(injector: Injector,
    public signalrService: SignalRService,
    public sanitizer: DomSanitizer,
    public madol: NzModalService) {
    // 注入服务组件等
    this.httpService = injector.get(HttpService);
    this.message = injector.get(NzMessageService);
    this.fb = injector.get(FormBuilder);
    this.nzModalService = injector.get(NzModalService);
    this.route = injector.get(ActivatedRoute);
    this.router = injector.get(Router);
    this.validateForm = this.fb.group({});
    this.nghttp = injector.get(HttpClient);
    this.location = injector.get(Location);
    // 数据内容处理
    this.isSpinning = true;
    this.iniObserable();
    this.signalrService.goToNextStep.subscribe(e => {
      if (this.recordId === e && e) {
        this.httpService.get<any>(`DrillRecord/GetCurrentIndex?recordId=${e}`).then(cindex => {
          this.goToSept(cindex);
        });
      }
    });
  }

  ngOnInit() {
    this.rb = document.getElementById('RightBox');
    this.rn = document.getElementById('RightBtn');
    this.route.queryParamMap
      .pipe(map(params => params.get('id') || null))
      .subscribe(e => {
        this.recordId = Number(e);
        if (!this.recordId) {
          this.message.error('无法确定主键信息!');
        } else {
          this.GetDataObserver.subscribe(sb => {
            this.currentIndex = this.flowRecordOutput['currentStep'];
          });
        }
      });
  }


  /**
   * 用于初始化，显示其他步骤数据内容的初始化。
   */
  iniObserable() {
    const this1 = this;
    this.GetDataObserver = Observable.create(async function (observer: Observer<any>) {
      const url = `DrillRecord/${this1.loginType === '0' ? 'GetAdminRecordFlowForm' : 'GetRecordFlowForm'}?recordId=
                  ${this1.recordId}&currentIndex=${this1.currentIndex !== undefined ? this1.currentIndex : 0}`;

      // 获取表单数据
      const res = await this1.httpService.get<any>(url);
      this1.flowRecordOutput = res;
      this1.subjectId = res.subjectId;
      this1.iniTeacherScore();
      // 获取指导文书
      this1._guideDocument = await this1.httpService.get<any>(`drillsubject/GetInfo?subjectId=${res.subjectId}&typeId=3`);
      this1.selectedTypeValue = res.rolePlayType;
      this1.errorMsgInfo = res.errorMessage;
      // 已经完成的演练，初始化演练时间线信息
      if (this1.flowRecordOutput.drillStatus && this1.flowRecordOutput.drillStatus <= 2 && this1.arLogHistory.length === 0) {
        this1.arLogHistory = await this1.httpService
          .get<any>(`DrillRecord/GetDrillRecordHistory?recordId=${this1.recordId}`);
      }
      this1.recordFlowId = res.recordFlowId;
      this1.setFormAndGetDataList(res.drillFormOutputs, observer);
      this1.reViewIndex = res.reViewIndex;
      if (this1.isOperation && res.drillStatus === 2) {
        this1.nzModalService.confirm({
          nzTitle: `确认`,
          nzContent: `演练已经完成是否要退出？`,
          nzZIndex: 1010,
          nzOnOk() {
            this1.goBack();
          }
        });
        this1.isOperation = false;
      }
    });
  }
  /**
   * 初始化教师打分列表
   */
  iniTeacherScore() {
    const maxScore = this.flowRecordOutput.maxTeacherScore;
    const result = new Array<number>();
    result.push(0);
    if (maxScore > 0) {
      for (let i = 0; i < maxScore; i++) {
        result.push(i + 1);
      }
    }
    this.teacherScoreArray = result;
  }

  /**
 * 从formgroup中获取值到传输模型
 *
 * @protected
 * @param {FormGroup} fb
 * @param {T} entity
 * @returns {T}
 * @memberof NgZorroPageBaseComponent
 */
  protected getEntityFromFormGroup(fb: FormGroup, entity: any): any {
    for (const key of Object.keys(fb.controls)) {
      entity[key] = fb.controls[key].value;
    }
    return entity;
  }

  /**
   * 模型值复制到formgroup
   *
   * @protected
   * @param {FormGroup} fb
   * @param {T} entity
   * @returns {*}
   * @memberof NgZorroPageBaseComponent
   */
  protected setEntityToFormGroup(fb: FormGroup, entity: any): FormGroup {
    for (const key of Object.keys(entity)) {
      if (fb.controls[key]) {
        fb.controls[key].setValue(entity[key]);
      }
    }
    return fb;
  }



  /**
    * 根据设置信息初始化表单、查询、数据格式化内容、并获取数据。
    * @param systemFormControl 系统设置信息
    */
  protected async setFormAndGetDataList(systemFormControl: Array<DrillFormControl>, observer: Observer<any>) {
    this.arTableFormControls = [];
    this.arSystemFormControls = systemFormControl == null ? [] : systemFormControl;
    // 根据表单设置，初始化验证内容。
    this.validateForm = this.iniFormGroup(this.arSystemFormControls);
    let maxRowIndex = 0;
    let findmaxRowspan = 0;
    // 获取最大行。
    this.arSystemFormControls.forEach(e => {
      const maxValue = e.inputRowIndex >= e.labelRowIndex ? e.inputRowIndex : e.labelRowIndex;
      if (maxValue > maxRowIndex) {
        maxRowIndex = maxValue;
        findmaxRowspan = e.labelRowSpan > e.inputRowSpan ? e.labelRowSpan : e.inputRowSpan;
      }
    });
    // 根据最大行，重新排序列表
    for (let i = 1; i <= maxRowIndex + findmaxRowspan; i++) {
      const findResult = this.arSystemFormControls
        .filter(e => (e.inputRowIndex === i || e.labelRowIndex === i) && e.showInForm)
        .sort((a, b) => (a.lableColIndex === 0 ? a.inputColIndex : a.lableColIndex) - (b.lableColIndex === 0 ? b.inputColIndex : b.lableColIndex));
      if (findResult) {
        this.arTableFormControls.push(findResult);
      }
    }
    //
    // this.arSystemFormControls
    //   .filter(e => e.inputRowIndex === 0 || e.labelRowIndex === 0)
    //   .forEach(e => {
    //     if (this.arTableFormControls.filter(e1 => e1.filter(s => s.fieldName === e.fieldName).length !== 0).length === 0) {
    //       this.arTableFormControls.push(new Array<DrillFormControl>(e));
    //     }
    //   });
    // 根据表单设置，初始化实体。
    for (const i of Object.keys(this.arSystemFormControls)) {
      const index = parseInt(i, 0);
      const fieldName = this.arSystemFormControls[index].fieldName;
      const entity = {};
      const formControl = this.arSystemFormControls[index];
      switch (formControl.fieldType) {
        case FieldType.Number:
          this.focusEntity[fieldName] = 0;
          break;
        case FieldType.Toggle:
          this.focusEntity[fieldName] = false;
          break;
        default:
          this.focusEntity[fieldName] = '';
          break;
      }

      if (formControl.remoteData &&
        (formControl.loadRemoteDataType === null || formControl.loadRemoteDataType === LoadRemoteDataType.LoadAll)) {
        const remoteurl = this.arSystemFormControls[index].remoteData;
        const dataResult =
          await this.httpService
            .get<Array<KeyValueOutput>>(
              remoteurl.indexOf('{PID}') !== -1
                ? `${remoteurl.replace('{PID}', this._pKeyFieldValue.toString())}`
                : `${this.arSystemFormControls[index].remoteData}`);
        if (Number(entity[fieldName])) {
          dataResult.forEach(e => e.dValue = parseInt(e.dValue, 0));
        } else if (Boolean(entity[fieldName])) {
          dataResult.forEach(e => e.dValue = Boolean(e.dValue));
        }
        this.arSystemFormControls[index].fieldData = dataResult;
      }
    }
    // 根据log信息，获取非文件信息
    if (this.flowRecordOutput.dataJson) {
      const dataSource = JSON.parse(this.flowRecordOutput.dataJson);
      this.focusEntity = { ...dataSource };
      // for (const pName of Object.keys(dataSource)) {
      //   if (this.focusEntity[pName] !== undefined) {
      //     this.focusEntity[pName] = dataSource[pName];
      //   }
      // }
    }

    // 根据log信息，获取文件信息
    if (this.flowRecordOutput.fileJson) {
      const dataSource = JSON.parse(this.flowRecordOutput.fileJson);
      for (const pName of Object.keys(dataSource)) {
        if (this.focusEntity[pName] !== undefined) {
          this.focusEntity[pName] = dataSource[pName];
        }
      }
    }
    this.isSpinning = false;
    observer.next(1);
  }

  /**
   * 根据设置初始化表单信息
   * @param input 系统表单设置
   */
  protected iniFormGroup(input: Array<SystemFormControl>): FormGroup {
    const group = {};
    if (input) {
      input.forEach(e => {
        if (e.inputRowIndex) {
          // 初始化上传文件组件
          if (e.fieldType === FieldType.Upload) {
            // this.fileList.push(new RecordFormUpLoadFile(e.fieldName, new Array<UploadFile>()));
            this.fileList[e.fieldName] = new Array<UploadFile>();
          }
          const arValids = [],
            controlConfig = [];
          controlConfig.push(null);
          if (e.isRequired) {
            arValids.push(Validators.required);
          }
          if (e.minLength) {
            arValids.push(Validators.minLength(e.minLength));
          }
          if (e.maxLength) {
            arValids.push(Validators.maxLength(e.maxLength));
          }
          if (e.remoteValid) {
            controlConfig.push({
              validators: arValids,
              updateOn: 'blur',
              // asyncValidators: [this.remoteAsyncValidator(e.fieldName, e.remoteValid)]
            });
          } else {
            controlConfig.push(arValids);
          }
          group[e.fieldName] = controlConfig;
        }
      });
    }
    // 审批意见
    group['opinion'] = [null, []];
    const formGroup = this.fb.group(group);
    return formGroup;
  }

  beforeUpload = (file: UploadFile): boolean => {
    const isLt2M = file.size / 1024 / 1024 < 2;
    if (!isLt2M) {
      this.message.error('文件大小超过2MB!');
    }
    return isLt2M;
  }

  bindingFormFile = (value) => {
    // this.fileList[value.name] = value.file;
    return Observable.create(function (observer: Observer<any>) { }).subscribe();
    // return new Observable().subscribe();
  }

  handleChange(info: any, fieldName: string) {
    const fileList = info.fileList.length > 0 ? [info.fileList[0]] : []; // info.fileList[0];
    this.fileList[fieldName] = fileList.filter(item => {
      item.status = 'done';
      return true;
    });
    this.focusEntity[fieldName] = this.fileList[fieldName].length > 0 ? '1' : '';
    this.validateForm.controls[fieldName].setValue(this.fileList[fieldName].length > 0 ? '1' : '');
    return Observable.create(function (observer: Observer<any>) { }).subscribe();
  }

  async addEntity(optype: number) {
    for (const i of Object.keys(this.validateForm.controls)) {
      this.validateForm.controls[i].markAsDirty();
      this.validateForm.controls[i].updateValueAndValidity();
    }
    if (!this.validateForm.valid) {
      return;
    }
    const formData = new Array<RecordUploadFile>();
    for (const name of Object.keys(this.fileList)) {
      if (this.fileList[name] && this.fileList[name].length > 0) {
        formData.push(new RecordUploadFile(name, this.fileList[name][0].name, this.fileList[name][0].thumbUrl));
      }
    }
    const formJson = JSON.stringify(this.arSystemFormControls);
    const dataJson = JSON.stringify(this.focusEntity);
    let msg = '';
    switch (optype) {
      case 6:
        msg = '提交';
        break;
      case 0:
        msg = '审批通过';
        break;
      case 1:
        msg = '审批退回';
        break;
      case 5:
        msg = '归档';
        break;
    }
    // 再次确认信息
    const thisInstance = this;
    if (this.focusEntity.opinion || optype !== 2) {
      this.nzModalService.confirm({
        nzTitle: `${msg}`,
        nzContent: `是否要【${msg}】该申请？`,
        nzZIndex: 1010,
        nzOnOk() {
          thisInstance.isOperation = true;
          return new Promise(async (resolve, reject) => {
            try {
              const result = await thisInstance.httpService.post<any>('DrillRecord/AddOperationLog',
                {
                  RecordFlowId: thisInstance.recordFlowId,
                  RecordId: thisInstance.recordId,
                  FlowStatus: optype === 2 ? 1 : optype,
                  FormJson: formJson,
                  DataJson: dataJson,
                  RecordUploadFiles: formData
                });
              thisInstance.signalrService.CallTheNextPerson(thisInstance.recordId.toString()).then(e => {
                if (e) {
                  thisInstance.httpService.get<any>(`DrillRecord/GetCurrentIndex?recordId=${e}`).then(cindex => {
                    thisInstance.goToSept(cindex);
                  });
                }
              });
              // window.location.reload();
              resolve();
            } catch (error) {
              window.location.reload();
              reject();
            }
          }).catch(e => {
            window.location.reload();
          });
        }
      });
    } else {
      this.message.error("请填写审批意见!");
    }

  }

  // getFileName(value: string): string {
  //   const findOne = this.fileList_sp.filter(e => e['FormName'] === value);
  //   if (findOne.length > 0) {
  //     return findOne[0].FileName;
  //   }
  // }

  // getFileUrl(value: string): string {
  //   const findOne = this.fileList_sp.filter(e => e['FormName'] === value);
  //   if (findOne.length > 0) {
  //     return this.httpService.IP_PORT + findOne[0].FileData;
  //   }
  // }
  /**
   * 判断是否BASE64还是URL
   * @param fieldName 字段值
   */
  protected isHaveImage(fieldName: string): boolean {
    return (<string>this.focusEntity[fieldName]).indexOf('/userfiles/') !== -1;
  }

  /**
   * 图片大小限制检查
   */
  beforeImgUpload = (file: File) => {
    const isJPG = (
      file.type === 'image/jpeg' ||
      file.type === 'image/png' ||
      file.type === 'image/gif' ||
      file.type === 'image/bmp'
    );
    if (!isJPG) {
      this.message.error('只能上传jpg文件!');
    }
    const isLt2M = file.size / 1024 / 1024 < 2;
    if (!isLt2M) {
      this.message.error('图片大小超过2MB!');
    }
    return isJPG && isLt2M;
  }
  /**
   * 用于附件绑定选择文件后的处理函数
   */
  bindingForm = (value) => {
    this.getBase64(value.file, (img: any) => {
      this.focusEntity[value.name] = img;
      this.validateForm.controls[value.name].setValue(img);
    });
    return Observable.create(function (observer: Observer<any>) { }).subscribe();
  }

  /**
   * 获取文件多base64码
   * @param img 文件
   * @param callback 回调函数
   */
  private getBase64(file: File, callback: (file: any) => void) {
    const reader = new FileReader();
    reader.addEventListener('load', () => callback(reader.result));
    reader.readAsDataURL(file);
  }

  goToSept(index: number) {
    if (index !== null) {
      this.reViewIndex = 0;
      this.isSpinning = true;
      this.currentIndex = index;
      this._focusEntity = {};
      this.arSystemFormControls = [];
      this.arTableFormControls = [];
      this.validateForm = this.fb.group({});
      this.arLogHistory = [];
      this.GetDataObserver.subscribe(sb => {
        this.isSpinning = false;
      });
    }
  }

  /**
 * 退回、返回
 */
  goBack() {
    this.location.back();
  }

  updateSubjectError() {
    const $this = this;
    this.nzModalService.confirm({
      nzTitle: `确认`,
      nzContent: `是否要更新模板演练设置？`,
      nzZIndex: 1010,
      async nzOnOk() {
        await $this.httpService.post('DrillRecord/UpdateSubjectError', { id: $this.recordId, rolePlayType: $this.selectedTypeValue, errorMessage: $this.errorMsgInfo });
        $this.message.success('保存成功');
      }
    });
  }

  showRight() {
    this.rn.style.right = '-74px';
    setTimeout(() => {
      this.rb.style.right = '0';
    }, 500);

  }

  hideRight() {
    this.rb.style.right = '-1000px';
    setTimeout(() => {
      this.rn.style.right = '0';
    }, 500);


  }

  showModal(): void {
    this.isVisible = true;
  }

  async saveTeacherScoreSet() {
    const postBody = {
      recordId: this.recordId,
      subjectId: this.flowRecordOutput.subjectId,
      scoreInfos: this.flowRecordOutput.teacherGroupScores
    };
    await this.httpService.post<any>('teacherinfo/GroupDrillTeacherSetScore', postBody);
    this.message.success('保存成功');
  }
  /**
   *  课程资料
   * @param entity 
   * @param tag 
   */
  showModalForFiles() {
    const keyValue = this.flowRecordOutput.subjectId;
    const subscription = this.nzModalService.create({
      nzTitle: `课程资料`,
      nzContent: GrillDataComponent,
      nzComponentParams: {
        pKeyFieldValue: keyValue
      },
      nzFooter: null,
      nzWidth: 700,
    });
  }
}
